﻿using System;
using System.Collections.Generic;
using System.Linq;

namespace Cjc.ExpressionEngine.Excel.Runtime.Types
{
	public struct Range
	{
		public CellId FromId { get; set; }
		private CellId ToId { get; set; }

		public Range( CellId fromId, CellId toId ) : this()
		{
			this.FromId = fromId;
			this.ToId = toId;
		}

		public Range( IEnumerable<CellId> cellIds ) : this()
		{
			var ids = cellIds.Take( 2 ).ToArray();

			this.FromId = ids[ 0 ];
			this.ToId = ( ids.Length > 1 ) ? ids[ 1 ] : ids[ 0 ];
		}

		public IEnumerable<Cell> GetCells( Worksheet worksheet )
		{
			return GetCells( worksheet, FromId, ToId );
		}

		public static IEnumerable<CellId> GetCellIds( IEnumerable<CellId> cellIds )
		{
			var ids = cellIds.ToArray();

			return ( ids.Length == 2 )
				? GetCellIds( ids[ 0 ], ids[ 1 ] )
				: ids;
		}

		public static IEnumerable<CellId> GetCellIds( CellId fromId, CellId toId )
		{
			return from c in Enumerable.Range( fromId.Column, toId.Column - fromId.Column + 1 )
				   from r in Enumerable.Range( fromId.Row, toId.Row - fromId.Row + 1 )
				   select new CellId( c, r );
		}

		public static IEnumerable<Cell> GetCells( Worksheet worksheet, CellId fromId, CellId toId )
		{
			return from id in GetCellIds( fromId, toId )
				   select worksheet.GetCell( id.Symbol );
		}
	}
}